iT邦幫忙

2024 iThome 鐵人賽

DAY 21
1

https://ithelp.ithome.com.tw/upload/images/20241005/20152073xmtY2QGTVD.png

前言

我們都知道 Core Web Vitals 的指標包含 LCP、INP、CLS,也經常探討如何提升這些指標的表現,但我們很少有機會去了解這些指標的閾值定義,而這些指標的閾值定義是基於研究室的研究數據,但實際上我們的網站效能可能會因為不同的網路環境、不同的裝置而有不同的表現,因此本篇文章將會介紹各指標的閾值定義,並且會提供一些實際的數據來說明這些閾值定義是否合理。

在此之前,先回顧一下指標門檻的定義:至少 10% 的網站需達到「良好」標準,而表現最差的 10-30% 則被歸類為「不良」。

LCP

https://web.dev/static/articles/lcp/image/good-lcp-values.svg?hl=zh-tw

Largest Contentful Paint(LCP) 用於衡量頁面加載的速度,標記頁面最主要內容完成加載的時間點。與傳統指標(如 load 或 DOMContentLoaded)不同,LCP 更準確地反映使用者在螢幕上實際看到的內容。

LCP 基於 Largest Contentful Paint API,當頁面首次繪製時,瀏覽器會生成一個 PerformanceEntry 事件,類型為 largest-contentful-paint,來標記當時頁面上最大的內容元素。如果後續渲染中出現更大的元素,瀏覽器會再次生成新的 PerformanceEntry 事件,更新 LCP 的時間點。例如:

  1. 首次繪製後:瀏覽器標記當時最大的內容元素(例如 <p><h1>)。
  2. 內容變更時:如果圖片或字體在後續加載中出現且比現有元素更大,瀏覽器會生成新的 LCP 事件。
  3. 頁面內容更新時:新加載的動態內容(如圖片或文字)比當前 LCP 元素更大時,會生成新的 LCP 事件。
  4. LCP 元素移除:如果最大的內容元素被移除,LCP 仍保持不變,除非有更大的元素被渲染。
  5. 使用者與頁面互動之前:LCP 報告會在使用者與頁面進行交互(如點擊、滾動)前停止,因為交互行為可能改變頁面可見的內容。

研究來源與評估

我們需要知道 LCP 的閾值評估會受到 FCP (First Contentful Paint)的影響,因為 LCP 通常發生在 FCP 之後。而 FCP 的「良好」門檻已經設定為 1 秒,再加上即時反應時間的定義是根據 Card 和 Miller 的研究:

  • Card 引用 Newell 的《統一認知理論》,將即時回應的時間範圍設定為 0.3 秒到 3 秒,理想的回應時間為 1 秒。
  • Miller 則指出,當回應延遲超過 2 秒時,使用者的任務執行會受到明顯影響,延遲每增加一秒,影響會更加顯著。

根據上述的研究,再加上 FCP 已占據的時間,可以推論出 LCP 的「良好」門檻可以被設定在 1 到 3 秒之間。然而,根據實驗數據和對網站效能的分析,最終選擇 2.5 秒 作為一致可達的「良好」門檻。細節的實驗會列出各種裝置所收集的數據進行分析,分析如下:

https://ithelp.ithome.com.tw/upload/images/20241005/20152073P3DeI8PzEE.png

可以發現,能達到 1 秒閾值的網頁只有不到 10 %,但 1.5 秒到 3 秒之間的所有其他閾值仍然是有效的候選。在對表現最佳的網站進行分析後,我們發現 1.5 秒和 2 秒的閾值並不一致可達,而 2.5 秒的閾值則是一致可達的。因此將 LCP 的閾值定義為 2.5 秒,這不僅符合實驗結果,也符合實際使用者的體驗。

https://ithelp.ithome.com.tw/upload/images/20241005/20152073oZIUs0lAff.png

如果設定 4 秒作為閾值,約有 26% 的手機網站和 21% 的桌面網站會被歸類為「不良」。這符合 10-30% 的目標範圍,因此得出 4 秒是一個可接受的「不良」閾值。

INP

https://web.dev/static/articles/inp/image/inp-desktop-v2.svg

INP(Interaction to Next Paint)是一個新的指標,從 2024 年 3 月起正式取代了 FID(First Input Delay)且 FID 也在 2024 年 9 月 11 日被淘汰。INP 考慮了整個頁面生命週期內的所有互動,而不僅僅是頁面載入後的第一次互動,因此能更準確地反映使用者體驗。

INP 會評估每次觸控、點擊或鍵盤與網頁互動時的延遲時間,並根據互動次數選取網頁互動延遲時間最低(或接近最高)的一個代表值,來表示網頁的整體回應速度。而這個延遲時間不會計算到整個互動的最終結果(例如伺服器回應或網絡請求的時間),而是注重從互動開始到瀏覽器進行下一次繪製的過程。例如下面動畫中點擊一個項目後,測量從點擊到顯示展開內容這種變化的時間。

https://imgur.com/OYsP99t

然而關於『互動』和『互動次數』在 Web Vitals 中也有明確的定義:

互動的定義

https://ithelp.ithome.com.tw/upload/images/20241005/2015207336Wjj2B524.png

在 Chrome 的分析中,使用者在頁面載入後有 90% 的時間都在與頁面互動,而在網頁上所謂的互動是進行例如點擊、觸控或鍵盤輸入等操作,這些操作會觸發一系列的 event handler
(如 pointerupmouseupclick),然而在操作到處發 event 的期間也會有延遲,這段時間也會被記錄,event 觸發後再啟動渲染和繪製工作,最後再繪製下一幀,即是一個完整的互動過程。

🔥 TIP
因此由上圖可以推出,以下三種情況都會影響 INP 的表現:

  1. 輸入延遲:從使用者與網頁互動時,直到互動 event 開始執行的時間。
  2. event 處理時間長度:包含 event 回調函數所需的執行時間。
  3. 顯示延遲,瀏覽器顯示下一個幀所需的時間,包含互動的視覺結果。

然而網頁上的互動有非常多種,但會被 INP 紀錄的只有以下三種:

  • 滑鼠點擊事件
  • 輕觸有觸控螢幕的裝置
  • 在實體鍵盤或螢幕鍵盤上按下按鍵

另外要特別注意的是,有些互動可能會發生在 iframe 中,例如影片撥放的點擊,但 JavaScript Web API 無法訪問 iframe 的內容,所以可能導致 CrUX 和 RUM 數據之間的差異。

INP 的計算方式

對於具有大量互動的頁面,偶然的問題可能會導致頁面上出現一個不正常的高延遲互動。互動次數越多,發生這種情況的機率越高。

所以為了更準確地測量這些頁面的實際響應性,每發生 50 次互動,就會忽略一個延遲最長的互動。大多數頁面不會有超過 50 次互動,因此通常 INP 所記錄的是最差的互動。

而頁面本身的測量會從所有瀏覽中的第 75 百分位數,排除離群值後提供大多數使用者的實際體驗值或更好的數據。

🔥關於憤怒點擊使互動增加
在 Chrome 的分析中發現,網頁回應速度緩慢會使點擊發生率上升,這種行為就稱為憤怒點擊,特別是在 CLS 和 INP 指標較不良的情況下容易發生。然而如果點擊過多,反而會再進一步拖慢回應速度,導致惡性循環。
https://docs.google.com/presentation/d/1Euu4FBL75z0I8UtKf3dTzrLYu6wxfeWnrmXUCn9AQIY/edit?usp=sharing&resourcekey=0-t6sEnmSbzYTO_fcrR8n9Jg
https://ithelp.ithome.com.tw/upload/images/20241005/20152073AV0A2NVy2L.png

研究與評估方式

雖然官方並沒有正式提供 INP 的閾值定義在 200ms 和 500ms 的原因,但可以從 FID 指標推論,例如下圖中 FID 的時間範圍是輸入延遲的期間,也就是紅色框起來的區域,而 FID 的閾值已經是 100ms, 300ms 所以合理推論再加上事件處理的時間與回應的延遲時間使得閾值為 200ms 和 500ms。

而 FID 的研究中也以 Michotte 的因果關係和 Miller 的控制觸發的回應為依據:

  • Michotte 的 The Perception of Causality,假設螢幕上有兩個物件,物件 A 與物件 B,兩者要有因果關係才為互動的依據:當物件 A 開始向物件 B 移動,一旦物件 A 接觸到物件 B 的瞬間即停止,同時物件 B 開始遠離物件 A ,研究中發現如果兩個物件之間的動作延遲約在 100 毫秒以內,可以視為物件 A 導致了物件 B 的動作,而若延遲時間在 100 毫秒到 200 毫秒之間,則會讓兩者的因果關係變得不確定,若是超過 200 毫秒則不再認為兩者的因果關係。
  • Miller 認為使用者進行物理操作(如按下按鍵或開關)時,系統如果在 0.1 秒內給出回應,會被感知為是與操作者的動作直接相關的。如果在 0.1 到 0.2 秒之內回應,則會讓使用者感覺這種回饋是即時的。

https://ithelp.ithome.com.tw/upload/images/20241005/20152073XHXJKDG4zZ.png

CLS

https://web.dev/static/articles/cls/image/good-cls-values.svg?hl=zh-tw

Cumulative Layout Shift (CLS) 是所謂的累計版面配置位移,這個指標主要是注重於視覺化內容穩定性,如果是非預期的版面配置位移可能會以多種方式乾擾使用者體驗,例如下方一個非常焦躁地動圖,使用者在閱讀文字時如果內容突然移動,導致點選錯誤的連結或按鈕,導致閱讀中斷或其他的行為,甚至會造成嚴重傷害。

Imgur

layout shift score

CLS 是由 Layout Instability API 定義的,當頁面上的可見元素在兩個畫面更新之間發生位移時,這些元素被稱為不穩定元素。與其他指標不同,CLS 的閾值沒有單位,因為它是根據計算出的 layout shift score 來衡量的。

瀏覽器在計算 layout shift score 時,會檢查可見元素在兩個畫面更新之間的位置變化,並根據以下兩個因素計算得出:

  1. 影響分數(Impact Fraction):表示移動的元素在視窗中佔用了多少區域。假設一個元素在頁面中佔了一半的區域,那影響分數就是 0.5。如果元素移動後佔據更大或更小的區域,會影響這個分數。例如下圖中位移後佔比分數大增:

    https://web.dev/static/articles/cls/image/impact-fraction-example-164341c82ee76_856.png?hl=zh-tw

  2. 距離分數(Distance Fraction):代表元素移動的距離有多遠,與視窗的寬或高相比。如果一個元素移動了視窗高度的四分之一,距離分數就是 0.25。例如下圖藍色箭頭的位移距離:

    https://web.dev/static/articles/cls/image/distance-fraction-example-9146d2a862482_856.png?hl=zh-tw

公式

layout shift score = Impact Fraction * Distance Fraction

範例

假設有一個元素移動後佔據了 75% 的視窗面積(影響分數是 0.75),並且它移動了 25% 的視窗高度(距離分數是 0.25)。因此,Layout Shift Score = 0.75 * 0.25 = 0.1875。

計算要點

  • 如果多個元素同時移動,它們的 Impact Fraction 和 Distance Fraction 會一起計算。
  • 如果某個元素移動到了視窗外,那視窗外的部分不會影響分數計算。
  • 如果只是新增元素或改變元素大小,但沒有推動其他可見元素改變位置,則不會影響分數計算。
  • 如果是在使用者輸入內容的 500 毫秒內發生位移,則會被標視為 hadRecentInput ,在計算時被排除。
  • 而適當地使用 CSS 的動畫和轉場效果也不會影響分數的計算,例如:transform: scale()transform: translate()

研究與評估方式

在 Chrome 的內部測試中,發現 CLS 超過 0.15 會被使用者認為具有干擾性,而 0.1 以下的變動則不會造成明顯干擾。因此,0.1 被加入「良好」的 CLS 候選閾值。

後來根據 CrUX 資料,接近 50% 的網站 CLS 分數在 0.05 以下,這是一個可行的目標。但由於某些情況下(如嵌入第三方內容)難以避免較大的布局變動,所以最後 0.1 被認為是在「體驗品質」與「可達性」之間的平衡點。

https://ithelp.ithome.com.tw/upload/images/20241005/201520735FA5qlgchJ.png

而不良標準的分析中,大約有 20% 的網站達到 CLS 分數為 0.25,也符合目標範圍的 10-30%。

https://ithelp.ithome.com.tw/upload/images/20241005/20152073BjCG8Sacz7.png

為什麼 INP 取代了 FID?

這個問題我想應該先從當初 Google 為什麼選擇使用 FID?當初 Google 認為 FID 是使用者在頁面載入後第一次與網頁互動到 event handler 可以執行的時間。這是當時他們認為可以非常實際地評估使用者體驗的方法。

後來也一直持續改進及開發一個新指標來擴展 FID 可以測量的範圍,並希望這個新指標可以符合以下幾點來反應更真實的使用者體驗:

  1. 考慮所有使用者輸入的回應速度,而不僅僅是第一次輸入。
  2. 捕捉每個事件的完整持續時間,而不僅僅是延遲部分。
  3. 將屬於同一邏輯互動的一系列事件進行分組,並將該互動的延遲定義為所有事件中持續時間最長的那一個。
  4. 為頁面生命週期中發生的所有互動創建一個綜合得分。

而從下圖的比較中可以看出 FID 和 INP 的比較,確實 INP 更完整地呈現使用者在與網頁互動後,頁面所進行的歷程,也因為 FID 有這兩個限制,所以最後被 INP 取代:

  • FID 只測量第一次輸入事件的延遲,忽略了後續可能也很慢的互動。
  • FID 不衡量從使用者互動到瀏覽器提供視覺反饋之間的完整延遲。

https://ithelp.ithome.com.tw/upload/images/20241005/20152073tnlAcamlpJ.png

為什麼實驗室資料與實際資料不同

我們一般在開發時多半會使用 Lighthouse 或是 Page Speed Insight (PSI) 作為網頁 Core Web Vitals 的測量,雖然 PSI 會參考 CrUX 和實驗室的資料,但從上一篇文章我們可以知道,如果實際使用者樣本數不足,最後還是使用實驗室的資料,因此造成我們在開發時會因為測量的方法都是實驗室數據,無法找出真正的指標問題點。

以 CLS 為例子,在 Lighthouse 中的數據永遠是【良好】,但等到 Search Console 每次取得 28 天的數據時,會一直呈現【不良】的狀態,這就是因為實驗室資料與實際資料不同,而原因可以為以下幾點:

  1. 研究室工具的限制:像 Lighthouse 這類實驗室工具,通常只測量頁面載入期間內容,主要聚焦於頁面首次載入的效能指標。這些工具在頁面加載完成後通常不會再繼續追蹤頁面變化,也無法捕捉。甚至有些實驗室工具沒有任何與網頁互動,因此不會回報網頁的 INP 指標。
  2. 實際資料的全面性:CrUX 資料集測量的是整個頁面生命週期內的指標,這包括了載入後的使用者互動及頁面變化。實際資料會捕捉到使用者在實際操作中遇到的延遲,例如點擊按鈕後的內容更新、滾動加載內容等情況。
  3. 載入後的變化
    • CLS:載入後的內容變動,例如延遲載入的圖片或滾動觸發的內容加載,可能導致 layout 偏移,這些偏移會被 CrUX 記錄,但不會被實驗室工具捕捉到。
    • LCP:如果載入後有額外的圖片或影片等內容延遲顯示,會影響 LCP 時間,這也會被 CrUX 記錄,而實驗室工具只測量首次載入的 LCP。
    • INP:頁面生命週期中的後續互動,例如使用者點擊按鈕或觸發單頁應用中的新內容更新,這些互動的延遲會被 CrUX 記錄,並影響最終的 INP 分數。

參考資料

https://web.dev/articles/inp
https://web.dev/blog/better-responsiveness-metric?hl=zh-tw
https://www.explainthis.io/zh-hant/swe/inp
https://vercel.com/blog/first-input-delay-vs-interaction-to-next-paint
https://web.dev/articles/optimize-cls?hl=zh-tw#lab-field


上一篇
靠 Grafana 吃飯的第二十天 - 深入了解前端效能監測與 Web Vitals
下一篇
靠 Grafana 吃飯的第二十二天 - 前端除了監控還需要可觀測性
系列文
論前端工程師如何靠 Grafana 吃飯:從 Grafana App 到前端可觀測性30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言